P12-1. 카오스 엔지니어링과 근본 원인 분리 종합 실습 - 이론 개념
P12-1. 카오스 엔지니어링과 근본 원인 분리 종합 실습 - 이론 개념
학습 목표
- **카오스 엔지니어링(Chaos Engineering)**의 핵심 철학과 정상 상태 가설(Steady-State Hypothesis) 기반 실험 설계 원리를 이해한다.
- 실무 장애 대응에서 가장 빈번하게 논쟁이 벌어지는 **"네트워크/메시 계층 지연(L7 Fault Delay)"**과 **"데이터베이스 락 경합 지연(PostgreSQL Row-Level Lock Contention)"**의 메커니즘 차이를 구조적으로 파악한다.
- **Istio Ambient Mesh(
ztunnel+waypoint)**와 **LGTM 스택(VictoriaMetrics·Loki·Tempo·Grafana·Kiali·postgres-exporter)**의 시그널을 교차 대조하여 단 1분 만에 근본 원인을 분리하는 RCA(Root Cause Analysis) 의사결정 트리를 마스터한다.
1. 카오스 엔지니어링(Chaos Engineering)의 본질
1.1 왜 고의로 장애를 주입하는가?
마이크로서비스와 하이브리드 클라우드(Kubernetes + 외부 VM DB) 아키텍처에서는 모든 컴포넌트가 정상일 때만 테스트해서는 실전 장애를 막을 수 없다.
용어 정리: 카오스 엔지니어링 (Chaos Engineering) & 정상 상태 가설 (Steady-State Hypothesis)
- 카오스 엔지니어링 (Chaos Engineering): 분산 시스템이 프로덕션 환경의 예측 불가능한 장애 상황을 견딜 수 있는지 확인하기 위해, 통제된 환경에서 의도적으로 장애(지연, 에러, 락 경합 등)를 주입하고 시스템의 반응과 관측 가능성(Observability)을 검증하는 공학적 실험 기법이다.
- 정상 상태 가설 (Steady-State Hypothesis): 실험 전 시스템이 정상적으로 동작하고 있음을 나타내는 정량적 기준선(예:
HTTP 200 성공률 99.9%,P99 응답 시간 < 50ms,pg_locks 대기 세션 0개)이다. - 폭발 반경 (Blast Radius): 주입한 장애가 영향을 미치는 범위다. Istio
VirtualService의 URI/헤더 매칭이나 특정 DB 행(WHERE id = 1)만 타겟팅하면 전체 서비스를 멈추지 않고 폭발 반경을 좁혀 안전하게 실험할 수 있다.
2. 실무 최대 난제: "네트워크가 느린가, DB가 느린가?"
클라이언트 입장에서는 네트워크/메시 구간에서 3초가 지연되든, 데이터베이스에서 Row Lock 때문에 5초가 지연되든 똑같이 **"API 응답이 수 초 동안 멈췄다"**고 느낀다. 관측 파이프라인이 없다면 네트워크/인프라 엔지니어와 백엔드/DBA 사이에 끝없는 책임 공방(Blame Game)이 벌어진다.
우리가 Part 01부터 Part 11까지 구축한 Ambient Mesh + LGTM + PostgreSQL 관측 파이프라인은 이 두 가지 장애를 전혀 다른 **지문(Fingerprint)**으로 즉시 구별해 낸다.
flowchart TB
subgraph ClientSide["클라이언트 체감 증상 (동일)"]
Symptom["API 응답 지연 발생 (3초 ~ 6초)"]
end
Symptom --> Check1{"1단계: Waypoint Access Log & Tempo Span 확인"}
Check1 -->|"DURATION=3005ms
UPSTREAM_SERVICE_TIME=3ms
RESPONSE_FLAGS=DI"| RootA["원인 A: 네트워크 / 메시 L7 계층 지연
(애플리케이션 및 DB는 3ms 만에 정상 처리)"]
Check1 -->|"DURATION=5000ms+
RESPONSE_FLAGS=-
(또는 PG TCP 세션 장시간 유지)"| Check2{"2단계: VictoriaMetrics & PostgreSQL 뷰 확인"}
Check2 -->|"pg_locks_count 상승
wait_event_type='Lock'
pg_blocking_pids() 존재"| RootB["원인 B: PostgreSQL Row-Level Lock 경합
(선행 미커밋 트랜잭션이 행 잠금 점유)"]
Check2 -->|"pg_locks 정상 (대기 없음)
wait_event_type='IO' / 'CPU'
pg_stat_statements mean_exec_time 급증"| RootC["원인 C: 비효율적 SQL 쿼리 / 인덱스 누락
(Full Table Scan 또는 디스크 I/O 병목)"]3. 시나리오별 관측 지문(Observability Fingerprint) 상세 비교
3.1 시나리오 A: 네트워크/메시 계층 지연 (Istio L7 Fault Delay)
Istio VirtualService를 통해 order-api의 /chaos-net 경로에 fixedDelay: 3s를 주입했을 때 각 계층에 남는 증거는 다음과 같다.
- Loki (Waypoint Envoy Access Log):
%DURATION%(전체 소요 시간):3005ms%RESP(X-ENVOY-UPSTREAM-SERVICE-TIME)%(실제 백엔드 파드가 처리한 시간):3ms%RESPONSE_FLAGS%:DI(Delay Injected)- 결론:
3005ms - 3ms = 3002ms가 백엔드 컨테이너 밖(프록시/네트워크 계층)에서 소비되었으며, 백엔드 애플리케이션은 단 3ms 만에 응답을 마쳤다!
- Tempo (분산 추적 Span):
- Span의 총 길이는
3.01s이지만, Span Attribute에response_flags = "DI"가 명시되어 있다.
- Span의 총 길이는
- VictoriaMetrics & PostgreSQL (
postgres-exporter):pg_stat_activity에 대기 중인 쿼리가0건이며,pg_locks_count변화도 전혀 없다.
3.2 시나리오 B: 데이터베이스 행 잠금 경합 (PostgreSQL Row-Level Lock Contention)
외부 VM 데이터베이스(pg-vm.mesh.internal, ordersdb)에서 선행 세션(Session 1)이 SELECT ... FOR UPDATE로 id = 1 행을 잠근 채 커밋하지 않고 있을 때, 후행 세션(Session 2)이 같은 행에 UPDATE를 시도하는 상황이다.
- Loki (Waypoint TCP Access Log):
inbound-vip|5432|tcp|pg-vm.mesh.internal로그의%DURATION%(세션 유지 시간)이 5,000ms ~ 7,000ms 이상으로 길어진다.%RESPONSE_FLAGS%는-(정상 TCP 스트림)이다. 즉, 네트워크 단절이나 프록시 지연 주입이 아님을 증명한다.
- VictoriaMetrics (
postgres-exporter메트릭):pg_locks_count{datname="ordersdb", mode="exclusivelock"}및rowexclusivelock수치가 상승한다.pg_stat_activity_count{datname="ordersdb", state="active"}및idle in transaction세션이 동시에 관측된다.
- PostgreSQL 내부 뷰 (
pg_stat_activity&pg_stat_statements):pg_stat_activity에서 지연 중인 세션의wait_event_type = 'Lock',wait_event = 'transactionid'가 선명하게 포착되며,pg_blocking_pids(pid)함수가 범인 세션의 PID를 정확히 지목한다.- 트랜잭션이 끝난 직후
pg_stat_statements를 조회하면 해당UPDATE구문의mean_exec_time(또는max_exec_time)이 수천 ms로 기록된다.
4. 두 시나리오의 핵심 지표 비교 요약표
| 관측 계층 및 지표 | 시나리오 A: 네트워크/메시 지연 (3s) |
시나리오 B: PostgreSQL Row Lock 경합 (6s) |
|---|---|---|
| 클라이언트 체감 응답 시간 | 약 3.0 ~ 3.3초 (지연) |
약 5.0 ~ 6.0초 (지연) |
Waypoint %DURATION% |
3005 ms |
TCP 세션 5000 ~ 7000 ms |
Waypoint upstream_service_time |
3 ms (백엔드는 즉시 응답!) |
- (TCP) 또는 백엔드 대기 시간 그대로 증가 |
Envoy %RESPONSE_FLAGS% |
DI (Delay Injected) |
- (네트워크/프록시 이상 없음) |
| Tempo Span 속성 | response_flags: "DI" |
DB 호출 구간 Span 길이 증가 |
PG wait_event_type / wait_event |
없음 (idle) |
Lock / transactionid |
PG pg_blocking_pids(pid) |
{} (빈 배열) |
{선행_세션_PID} (블로커 즉시 특정) |
PG pg_stat_statements 실행 시간 |
변화 없음 (< 1ms) |
UPDATE 쿼리 실행 시간 5000ms+ 폭증 |
5. 종합 아키텍처 회고: Part 00 ~ Part 12 전체 여정
이로써 우리는 단일 클러스터와 외부 VM을 아우르는 엔터프라이즈급 Service Mesh & Observability 풀스택 아키텍처를 바닥부터 직접 설계하고 검증했다.
- 인프라 & 데이터플레인 (Part 00 ~ Part 05):
- 3노드 Kubernetes 클러스터 위에 사이드카 없는 **Istio Ambient Mesh (
ztunnelL4 +waypointL7)**를 구축하고, HBONE(:15008) mTLS 암호화, SPIFFE ID 기반 Zero-Trust 인가, 카나리 라우팅, 서킷 브레이커를 완성했다.
- 3노드 Kubernetes 클러스터 위에 사이드카 없는 **Istio Ambient Mesh (
- 하이브리드 VM 확장 & DB 아키텍처 (Part 06 ~ Part 07):
- 클러스터 외부의 **PostgreSQL 18 VM(
study-pg-vm)**을ServiceEntry·WorkloadEntry로 메시에 편입시키고, MVCC 튜플 구조(ctid), Vacuum, Row Lock, Terraform IaC 설계를 검증했다.
- 클러스터 외부의 **PostgreSQL 18 VM(
- LGTM 통합 관측성 & 카오스 검증 (Part 08 ~ Part 12):
- 차세대 통합 수집기 Grafana Alloy를 중심으로 VictoriaMetrics(Metrics) · Loki(Logs) · Tempo(Traces) · Grafana · Kiali를 연결하여, 어떠한 복합 장애가 발생하더라도 **데이터에 기반해 1분 안에 근본 원인을 분리(RCA)**할 수 있는 관측 체계를 완성했다.
네비게이션
| 이전 | 목록 | 다음 |
|---|---|---|
| ◀ Part 11 실습 | 목록으로 | Part 12 실습 ▶ |